﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Threading;
using System.Net;
using System.Net.Sockets;
using System.IO;

namespace Client
{
    public partial class video : Form
    {
        protected String prova;
        private TcpClient client;
        private Socket s;
        private const int DIM = 200000;
        private byte[] buf = new byte[DIM];
        private Thread receive_img;
        private MemoryStream ms;
        private object o;
        public delegate void cursor(string txt);
        private cursor curpos;
        public delegate void imagerectdraw(Rectangle rect, Image imm);
        private imagerectdraw drawrect;
        
        public void drawimrect(Rectangle rect, Image image)
        {
            Brush tBrush = new TextureBrush(new Bitmap(image));
            Graphics g=imm.CreateGraphics();
            g.FillRectangle(tBrush, rect);
            g.Dispose();
        }

        public Thread rec_img
        {
            get { return receive_img; }
        }


        private void write_cur(string txt)
        {
            cur_pos.Text = txt;
        }

        private const int CP_NOCLOSE_BUTTON = 0x200;
        
        public video(TcpClient c)
        {
            InitializeComponent();
            client = c;
            curpos = new cursor(write_cur);
            drawrect = new imagerectdraw(drawimrect);
            s= new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
            s.Bind(new IPEndPoint(IPAddress.Any,0));
            receive_img = new Thread(Receive);
            receive_img.Start();
            o = new object();
        }
        private void Receive()
        {
            bool flag = true;
            while (flag)
            {
                ms = new MemoryStream();
                try
                {
                    BinaryReader stream = new BinaryReader(client.GetStream());
                    Monitor.Enter(o);
                    int i = stream.ReadInt32();
                    if (i != -1)
                    {
                        if (i != -2)
                        {
                            int x = stream.ReadInt32();
                            int y = stream.ReadInt32();
                            int width = stream.ReadInt32();
                            int height = stream.ReadInt32();
                            byte[] buf = stream.ReadBytes(i);
                            MemoryStream mems = new MemoryStream(buf);
                            Image temp = Image.FromStream(mems);
                            object[] obj = new object[2];
                            obj[0] =new Rectangle(x, y, width, height); 
                            obj[1]=temp;
                            Invoke(drawrect,obj);
                            Monitor.Exit(o);
                        }
                        else
                        {
                            int x = stream.ReadInt32();
                            int y = stream.ReadInt32();
                            if (x != -1 && y != -1)
                            {
                                Point p=new Point(x,y);
                                Invoke(curpos, "present");
                                //Invoke(dcursor, p);
                            }
                            else
                            {
                                Invoke(curpos, "not present");
                            }
                        }
                    }
                    else
                    {
                        MessageBox.Show("Window closed");
                    }
                }
                catch
                {
                    ;
                }
            }
        }
        private void byteArrayToImage(byte[] byteArrayIn)
        {
            try
            {
                
                MemoryStream ms = new MemoryStream(byteArrayIn);
                Image returnImage = Image.FromStream(ms);
                imm.Image = returnImage;
                
            }
            catch
            {
                ;
            }
        }
        protected override void OnPaint(PaintEventArgs e)
        {
            // If there is an image and it has a location, 
            // paint it when the Form is repainted.
            int i = 1;
            try
            {
                client.GetStream().Write(BitConverter.GetBytes(i), 0, 4);
            }
            catch
            {
                MessageBox.Show("Disconnected");
                this.Close();
            }
            //MessageBox.Show("lol");
            //imm.Image = (Image)new Bitmap(512, 400);
        }
        protected override CreateParams CreateParams
        {
            get
            {
                CreateParams myCp = base.CreateParams;
                myCp.ClassStyle = myCp.ClassStyle | CP_NOCLOSE_BUTTON;
                return myCp;
            }
        }
    }
}
